﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using System.IO;
using System.Net;
using System.Drawing;
using System.Windows.Forms.DataVisualization.Charting;
using Newtonsoft.Json;
using ServiceStack.Redis;

namespace PM25
{
    public partial class Form1 : Form
    {
        public const int SevenDays = 7;
        Dictionary<string, string> dict7Days2Pm25 = new Dictionary<string, string>();
        Weather weather = new Weather();
        WeatherDays weatherDays = new WeatherDays();
        String redishost = "127.0.0.1";
        int redisport = 6379;

        public Form1()
        {
            InitializeComponent();
            
            //加载所有皮肤列表
            //this.skinEngine1.SkinFile = "DiamondBlue.ssk";

            //timerTime.Start();
            timerGetWeather.Start();
            panel1.BackColor = Color.FromArgb(25, 204, 212, 230);
            panel2.BackColor = Color.FromArgb(25, 204, 212, 230);
            panel3.BackColor = Color.FromArgb(25, 204, 212, 230);
            panel11.BackColor = Color.FromArgb(25, 204, 212, 230);

            //颜色示例
            panel5.BackColor = Color.FromArgb(82, 251, 43);
            panel6.BackColor = Color.FromArgb(237, 196, 30);
            panel7.BackColor = Color.FromArgb(246, 122, 42);
            panel8.BackColor = Color.FromArgb(207, 75, 60);
            panel9.BackColor = Color.FromArgb(201, 22, 39);

            //启动时采集失败，重复采集一次；定时采集失败不重复采集
            if(false == GetWeather2())
            {
                if(false == GetWeather2())
                {
                    MessageBox.Show("实时天气数据采集失败！");
                    //数据抓取失败，不显示，暂时不退出
                    //System.Environment.Exit(0);
                }
            }
            if(false == GetRealTimePM25())
            {
                if (false == GetRealTimePM25())
                {
                    MessageBox.Show("实时PM2.5数据采集失败！");
                    //数据抓取失败，不显示，暂时不退出
                    //System.Environment.Exit(0);
                }
            }
            if(false == GetDays7())
            {
                if (false == GetDays7())
                {
                    MessageBox.Show("历史天气数据采集失败！");
                    //数据抓取失败，不显示，暂时不退出
                    //System.Environment.Exit(0);
                }
            }
            
            InitChart();
            
        }

        private bool GetWeather2()
        {
            WebClient web = new WebClient();
            web.Encoding = Encoding.UTF8;
            string jsonData = web.DownloadString("https://www.tianqiapi.com/api/?version=v6&appid=58661542&appsecret=is3N7hMl&cityid=101030100");//这一句话就能请求到数据了
            weather = JsonConvert.DeserializeObject<Weather>(jsonData);

            RedisClient redisClient = new RedisClient(redishost, redisport);
            //将时间间隔ts3初始化为7天0小时0分0秒0毫秒
            //显示过去一周的历史，实际存储时间6天就够了
            TimeSpan timeSpan = new TimeSpan(7, 0, 0, 0, 0);
            try
            {
                //该方法只能记录昨天最后一次的数据作为昨天的值
                //redisClient.Set(weather.date, weather.air,timeSpan);

                //本方法修改为每次的值都记录，便于显示时求平均值
                byte[][] hkeys = redisClient.HGetAll(weather.date);
                int index = hkeys.Length;
                redisClient.HSet(weather.date, System.Text.Encoding.Default.GetBytes(index.ToString()),
                        System.Text.Encoding.Default.GetBytes(weather.air));
                redisClient.Expire(weather.date, Convert.ToInt32(timeSpan.TotalSeconds));
            }
            catch(Exception e)
            {
                MessageBox.Show(e.Message);
            }
            return true;
        }

        private bool GetDays7()
        {
            try
            {
                RedisClient redisClient = new RedisClient(redishost, redisport);
                List<string> listKeys = redisClient.GetAllKeys();
                listKeys.Sort();
                foreach (string key in listKeys)
                {
                    if (!key.Equals(DateTime.Now.ToString("yyyy-MM-dd")))
                    {
                        //处理昨天最后一次采集作为历史的逻辑
                        //byte[] byteValue = redisClient.Get(key);
                        //String value = System.Text.Encoding.Default.GetString(byteValue);

                        //处理哈希存储每天采集，求平均值
                        byte[][] hkeys = redisClient.HGetAll(key);
                        int value = 0;
                        for(int i = 1;i <= hkeys.Length;)
                        {
                            String curVal = System.Text.Encoding.Default.GetString(hkeys[i]);
                            value += Convert.ToInt32(curVal);
                            i += 2;
                        }
                        value = value / (hkeys.Length / 2);
                        //**********结束*********************

                        if (!dict7Days2Pm25.ContainsKey(key))
                        {
                            dict7Days2Pm25.Add(key, value.ToString());
                        }
                        else
                        {
                            dict7Days2Pm25[key] = value.ToString();
                        }
                    }
                }
            }catch(Exception e)
            {
                MessageBox.Show(e.Message);
            }

            return true;
        }

        /// <summary>
        /// 获取实施pm2.5
        /// </summary>
        private bool GetRealTimePM25()
        {
            //获取pm2.5
            string aqi = weather.air;
            string pm25 = weather.air_pm25;
            
            labelAQI.Text = aqi;
            labeldate.Text = pm25;
            label3.Text = "天津";

            //if (listWeather.Count == 2)
            //{
            labelDay1.Text = weather.wea;
            labelDay2.Text = weather.tem;

            lalhumidity.Text = weather.humidity;
            labelwind.Text = weather.win;
            labelWindSpeed.Text = weather.win_speed;
            //}
            labeldate.Text = weather.date;
            labelweek.Text = weather.week;

            if (Convert.ToInt32(aqi) >= 300)
            {
                pictureBox1.Image = Image.FromFile("./img/level5.png");
                labelAQI.ForeColor = System.Drawing.Color.FromArgb(201, 22, 39);
                labelQuality.ForeColor = System.Drawing.Color.FromArgb(201, 22, 39);
                labelQuality.Text = "严重";
            }
            else if(Convert.ToInt32(aqi) >= 200)
            {
                pictureBox1.Image = Image.FromFile("./img/level4.png");
                labelAQI.ForeColor = System.Drawing.Color.FromArgb(207, 75, 60);
                labelQuality.ForeColor = System.Drawing.Color.FromArgb(207, 75, 60);
                labelQuality.Text = "重度";
            }
            else if (Convert.ToInt32(aqi) >= 150)
            {
                pictureBox1.Image = Image.FromFile("./img/level3.png");
                labelAQI.ForeColor = System.Drawing.Color.FromArgb(246, 122, 42);
                labelQuality.ForeColor = System.Drawing.Color.FromArgb(246, 122, 42);
                labelQuality.Text = "中度";
            }
            else if (Convert.ToInt32(aqi) >= 100)
            {
                pictureBox1.Image = Image.FromFile("./img/level2.png");
                labelAQI.ForeColor = System.Drawing.Color.FromArgb(237, 196, 30);
                labelQuality.ForeColor = System.Drawing.Color.FromArgb(237, 196, 30);
                labelQuality.Text = "轻度";
            }
            else 
            {
                pictureBox1.Image = Image.FromFile("./img/level1.png");
                labelAQI.ForeColor = System.Drawing.Color.FromArgb(82, 251, 43);
                labelQuality.ForeColor = System.Drawing.Color.FromArgb(82, 251, 43);
                labelQuality.Text = "优良";
            }
            return true;
        }

        private void timerGetWeather_Tick(object sender, EventArgs e)
        {
            
            GetWeather2();
            GetDays7();
            GetRealTimePM25();
            InitChart();
        }

        private void InitChart()
        {
            Series series = chart1.Series[0];
            series.Points.Clear();
            series.Label = "#VAL";

            int i = 0;

            foreach (var item in dict7Days2Pm25)
            {
                series.Points.AddXY(item.Key, item.Value);
                series.Points[i].Color = System.Drawing.Color.FromArgb(82, 251, 43);
                if (Convert.ToDouble(item.Value) > 300)
                {
                    series.Points[i].Color = System.Drawing.Color.FromArgb(201, 22, 39);
                }
                else if (Convert.ToDouble(item.Value) > 200)
                {
                    series.Points[i].Color = System.Drawing.Color.FromArgb(207, 75, 60);
                }
                else if (Convert.ToDouble(item.Value) > 150)
                {
                    series.Points[i].Color = System.Drawing.Color.FromArgb(246, 122, 42);
                }
                else if (Convert.ToDouble(item.Value) > 100)
                {
                    series.Points[i].Color = System.Drawing.Color.FromArgb(237, 196, 30);
                }
                else
                {
                    series.Points[i].Color = System.Drawing.Color.FromArgb(82, 251, 43);
                }
                i++;
            }
        }

        private void Form1_FormClosing(object sender, FormClosingEventArgs e)
        {
            DialogResult dr = MessageBox.Show("确认关闭系统吗？", "提示", MessageBoxButtons.OKCancel);
            if (dr == DialogResult.OK)
            {
                //用户选择确认的操作
                System.Environment.Exit(0);
                e.Cancel = false;
            }
            else if (dr == DialogResult.Cancel)
            {
                //用户选择取消的操作
                e.Cancel = true;
                return;
            }
        }
    }
 }
